package com.haixiaoke.saas.order.service.impl;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONUtil;
import com.haixiaoke.saas.apartment.domain.HousingAllocation;
import com.haixiaoke.saas.apartment.service.IHousingAllocationService;
import com.haixiaoke.saas.common.constant.HouseConstants;
import com.haixiaoke.saas.common.constant.LockConstants;
import com.haixiaoke.saas.common.constant.OrderConstants;
import com.haixiaoke.saas.common.core.text.Convert;
import com.haixiaoke.saas.common.enums.OrderStateEnum;
import com.haixiaoke.saas.common.exception.ServiceException;
import com.haixiaoke.saas.common.tenant.TenantContext;
import com.haixiaoke.saas.common.utils.DateUtils;
import com.haixiaoke.saas.common.utils.GsonUtil;
import com.haixiaoke.saas.lock.domain.LockFace;
import com.haixiaoke.saas.lock.domain.LockPwd;
import com.haixiaoke.saas.lock.service.IHouseLockService;
import com.haixiaoke.saas.lock.service.ILockFaceService;
import com.haixiaoke.saas.lock.service.ILockPwdService;
import com.haixiaoke.saas.order.domain.CheckOutOrder;
import com.haixiaoke.saas.order.domain.Order;
import com.haixiaoke.saas.order.domain.OrderHouseInspection;
import com.haixiaoke.saas.order.domain.OrderRefundItem;
import com.haixiaoke.saas.order.mapper.OrderHouseInspectionMapper;
import com.haixiaoke.saas.order.service.ICheckOutOrderService;
import com.haixiaoke.saas.order.service.IOrderHouseInspectionService;
import com.haixiaoke.saas.order.service.IOrderRefundItemService;
import com.haixiaoke.saas.order.service.IOrderService;
import com.haixiaoke.saas.order.state.server.IOrderStateServerRole;
import com.haixiaoke.saas.order.state.server.OrderStateServerRole;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.Map;

import static com.haixiaoke.saas.system.framework.security.util.SecurityUtils.getUsername;

/**
 * 订单验房信息Service业务层处理
 *
 * @author qixi
 * @date 2024-04-09
 */
@Service
public class OrderHouseInspectionServiceImpl implements IOrderHouseInspectionService {
    @Autowired
    private OrderHouseInspectionMapper orderHouseInspectionMapper;

    @Autowired
    private IOrderService orderService;

    @Autowired
    private IOrderRefundItemService orderRefundItemService;
    @Autowired
    private ICheckOutOrderService checkOutOrderService;
    @Autowired
    private IHousingAllocationService housingAllocationService;
    @Autowired
    private IHouseLockService houseLockService;
    @Autowired
    private ILockFaceService lockFaceService;
    @Autowired
    private ILockPwdService lockPwdService;

    /**
     * 查询订单验房信息
     *
     * @param inspectionId 订单验房信息主键
     * @return 订单验房信息
     */
    @Override
    public OrderHouseInspection selectOrderHouseInspectionByInspectionId(Long inspectionId) {
        OrderHouseInspection orderHouseInspection = orderHouseInspectionMapper.selectOrderHouseInspectionByInspectionId(inspectionId);
        return getOrderHouseInspection(orderHouseInspection);
    }


    /**
     * 查询订单验房信息列表
     *
     * @param orderHouseInspection 订单验房信息
     * @return 订单验房信息
     */
    @Override
    public List<OrderHouseInspection> selectOrderHouseInspectionList(OrderHouseInspection orderHouseInspection) {
        List<OrderHouseInspection> orderHouseInspections = orderHouseInspectionMapper.selectOrderHouseInspectionList(orderHouseInspection);
        orderHouseInspections.forEach(x -> {
            String facilityDetails = x.getFacilityDetails();
            if (StrUtil.isNotBlank(facilityDetails)) {
                List<Map<String, Object>> bean = GsonUtil.toListMap(facilityDetails);
                x.setFacilityDetailList(bean);
            }

            String houseImgs = x.getHouseImgs();
            if (StrUtil.isNotBlank(houseImgs)) {
                List<String> split = StrUtil.split(houseImgs, ',');
                x.setHouseImgsList(split);
            }
        });
        return orderHouseInspections;
    }

    /**
     * 新增订单验房信息
     *
     * @param orderHouseInspection 订单验房信息
     * @return 结果
     */
    @Override
    public int insertOrderHouseInspection(OrderHouseInspection orderHouseInspection) {
        orderHouseInspection.setCreateTime(DateUtils.getNowDate());
        List<String> houseImgsList = orderHouseInspection.getHouseImgsList();
        if (CollectionUtil.isNotEmpty(houseImgsList)) {
            String join = CollectionUtil.join(houseImgsList, ",");
            orderHouseInspection.setHouseImgs(join);
        }

        List<Map<String, Object>> facilityDetailList = orderHouseInspection.getFacilityDetailList();
        if (CollectionUtil.isNotEmpty(facilityDetailList)) {
            String jsonStr = JSONUtil.toJsonStr(facilityDetailList);
            orderHouseInspection.setFacilityDetails(jsonStr);
        }

        return orderHouseInspectionMapper.insertOrderHouseInspection(orderHouseInspection);
    }

    /**
     * 修改订单验房信息
     *
     * @param orderHouseInspection 订单验房信息
     * @return 结果
     */
    @Override
    public int updateOrderHouseInspection(OrderHouseInspection orderHouseInspection) {
        orderHouseInspection.setUpdateTime(DateUtils.getNowDate());
        return orderHouseInspectionMapper.updateOrderHouseInspection(orderHouseInspection);
    }

    /**
     * 批量删除订单验房信息
     *
     * @param inspectionIds 需要删除的订单验房信息主键
     * @return 结果
     */
    @Override
    public int deleteOrderHouseInspectionByInspectionIds(Long[] inspectionIds) {
        return orderHouseInspectionMapper.deleteOrderHouseInspectionByInspectionIds(inspectionIds);
    }

    /**
     * 删除订单验房信息信息
     *
     * @param inspectionId 订单验房信息主键
     * @return 结果
     */
    @Override
    public int deleteOrderHouseInspectionByInspectionId(Long inspectionId) {
        return orderHouseInspectionMapper.deleteOrderHouseInspectionByInspectionId(inspectionId);
    }

    @Override
    @Transactional
    public int houseInspection(OrderHouseInspection orderHouseInspection) {
        String orderId = orderHouseInspection.getOrderId();
        Order order = orderService.selectOrderByOrderId(orderId);

        if ( !(StrUtil.equals(OrderStateEnum.ORDER_STATE_REFUND_RENT.getValue(), order.getOrderState()) ||
                StrUtil.equals(OrderStateEnum.ORDER_STATE_OVERTIME_REFUND_RENT.getValue(), order.getOrderState()))) {
            throw new ServiceException("订单状态异常，请刷新后再试");
        }

        orderHouseInspection.setTenantId(TenantContext.getTenantId());
        orderHouseInspection.setApplicationTime(order.getCheckOutApplicationTime());
        orderHouseInspection.setHouseId(order.getHouseId());
        orderHouseInspection.setRefundRentTime(order.getRealityCheckOutTime());
        orderHouseInspection.setCreateBy(getUsername());


        int i = this.insertOrderHouseInspection(orderHouseInspection);

        // 修改订单状态
        IOrderStateServerRole orderStateServerRole = new OrderStateServerRole(order);
        orderStateServerRole.houseInspection();


        // 根据房屋ID和用户类型删除锁密码和锁人脸信息
        houseLockService.removeLockPwdAndLockFace(order.getHouseId(), LockConstants.USER_TYPE_TENANT);

        return i;
    }


    @Override
    public OrderHouseInspection selectOrderHouseInspectionByOrderId(String orderId) {
        OrderHouseInspection orderHouseInspection = orderHouseInspectionMapper.selectOrderHouseInspectionByOrderId(orderId);
        return getOrderHouseInspection(orderHouseInspection);
    }

    @Override
    @Transactional
    public int apartmentHouseInspection(OrderHouseInspection orderHouseInspection) {
        String orderId = orderHouseInspection.getOrderId();
        Date nowDate = DateUtils.getNowDate();
        Order order = orderService.selectOrderByOrderId(orderId);
        orderHouseInspection.setApplicationTime(order.getCheckOutApplicationTime());
        orderHouseInspection.setHouseId(order.getHouseId());
        orderHouseInspection.setRefundRentTime(order.getRealityCheckOutTime());

        orderHouseInspection.setCreateTime(DateUtils.getNowDate());
        List<String> houseImgsList = orderHouseInspection.getHouseImgsList();
        if (CollectionUtil.isNotEmpty(houseImgsList)) {
            String join = CollectionUtil.join(houseImgsList, ",");
            orderHouseInspection.setHouseImgs(join);
        }

        // 验房时间更新
        CheckOutOrder checkOutOrder = checkOutOrderService.selectCheckOutOrderByOrderId(orderId);
        checkOutOrder.setInspectionTime(nowDate);
        checkOutOrderService.updateCheckOutOrder(checkOutOrder);

        List<Map<String, Object>> facilityDetailList = orderHouseInspection.getFacilityDetailList();
        if (HouseConstants.HOUSE_STATE_DAMAGE.equals(orderHouseInspection.getHouseState())
                && CollectionUtil.isNotEmpty(facilityDetailList)) {
            String jsonStr = JSONUtil.toJsonStr(facilityDetailList);
            orderHouseInspection.setFacilityDetails(jsonStr);

            BigDecimal totalPrice = BigDecimal.ZERO;
            for (Map<String, Object> map : facilityDetailList) {
                totalPrice = totalPrice.add(BigDecimal.valueOf(Convert.toDouble(map.get("price"))));
            }
            OrderRefundItem refundItem = new OrderRefundItem();
            refundItem.setOrderId(orderId);
            refundItem.setHouseId(order.getHouseId());
            refundItem.setRefundType(OrderConstants.REFUND_TYPE_FACILITY);
            refundItem.setRefundQuantity(BigDecimal.valueOf(facilityDetailList.size()));
            refundItem.setTenantId(order.getTenantId());
            refundItem.setItemSum(totalPrice);
            refundItem.setCreateBy(orderHouseInspection.getCreateBy());
            refundItem.setCreateTime(nowDate);
            refundItem.setCheckOutOrderId(checkOutOrder.getCheckOutOrderId());
            HousingAllocation allocation = housingAllocationService.selectHousingAllocationByHouseId(order.getHouseId());
            refundItem.setAllocationId(allocation.getAllocationId());
            orderRefundItemService.insertOrderRefundItem(refundItem);

        }

        return orderHouseInspectionMapper.insertOrderHouseInspection(orderHouseInspection);
    }

    private OrderHouseInspection getOrderHouseInspection(OrderHouseInspection orderHouseInspection) {
        if (ObjectUtil.isNotEmpty(orderHouseInspection)) {
            String facilityDetails = orderHouseInspection.getFacilityDetails();
            if (StrUtil.isNotBlank(facilityDetails)) {
                List<Map<String, Object>> bean = GsonUtil.toListMap(facilityDetails);
                orderHouseInspection.setFacilityDetailList(bean);
            }

            String houseImgs = orderHouseInspection.getHouseImgs();
            if (StrUtil.isNotBlank(houseImgs)) {
                List<String> split = StrUtil.split(houseImgs, ',');
                orderHouseInspection.setHouseImgsList(split);
            }
        }

        return orderHouseInspection;
    }
}
